package com.bjbn.service.impl;

import com.bjbn.bean.MonitorResponse;
import com.bjbn.bean.QueueInfo;
import com.bjbn.service.RabbitmqMonitorService;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Service;

import javax.annotation.PostConstruct;
import java.time.LocalDateTime;
import java.time.temporal.ChronoUnit;
import java.util.List;
import java.util.Map;
import java.util.concurrent.ConcurrentHashMap;
import java.util.stream.Collectors;

/**
 * RabbitMQ监控服务实现类
 * 
 * @author bjbn
 */
@Slf4j
@Service
public class RabbitmqMonitorServiceImpl implements RabbitmqMonitorService {

    @Value("${monitor.data-retention-minutes:60}")
    private int dataRetentionMinutes;
    
    @Value("${monitor.delay-threshold-seconds:300}")
    private int delayThresholdSeconds;
    
    @Value("${monitor.no-data-threshold-seconds:3600}")
    private int noDataThresholdSeconds;
    
    @Value("${rabbitmq.queue.name}")
    private String queueName;

    /**
     * 队列信息缓存
     */
    private final Map<String, QueueInfo> queueCache = new ConcurrentHashMap<>();

    /**
     * 初始化队列列表
     */
    @PostConstruct
    @Override
    public void initializeQueues() {
        log.info("初始化RabbitMQ队列列表...");
        
        // 初始化需要监控的队列
        addQueue(queueName, "雷达数据队列", "00001");
        
        log.info("RabbitMQ队列列表初始化完成，共{}个队列", queueCache.size());
    }

    /**
     * 添加队列
     */
    private void addQueue(String queueName, String description, String code) {
        QueueInfo queueInfo = new QueueInfo(queueName, description, code, null, null, null, null, 0);
        queueInfo.setStatus("NO_DATA");
        queueCache.put(queueName, queueInfo);
    }

    @Override
    public MonitorResponse getMonitorStatus() {
        LocalDateTime currentTime = LocalDateTime.now();
        List<QueueInfo> queues = getAllQueues();
        
        // 更新每个队列的状态和时间差
        queues.forEach(this::updateQueueStatus);
        
        return new MonitorResponse(200, "获取监控状态成功", currentTime, queues);
    }

    @Override
    public QueueInfo getQueueStatus(String queueName) {
        QueueInfo queueInfo = queueCache.get(queueName);
        if (queueInfo != null) {
            updateQueueStatus(queueInfo);
        }
        return queueInfo;
    }

    @Override
    public List<QueueInfo> getAllQueues() {
        return queueCache.values().stream()
                .sorted((q1, q2) -> q1.getCode().compareTo(q2.getCode()))
                .collect(Collectors.toList());
    }

    @Override
    public void updateQueueLastDataTime(String queueName) {
        QueueInfo queueInfo = queueCache.get(queueName);
        if (queueInfo != null) {
            LocalDateTime now = LocalDateTime.now();
            queueInfo.setLastDataTime(now);
            queueInfo.setUpdateTime(now);
            queueInfo.setMessageCount(queueInfo.getMessageCount() + 1);
            log.debug("更新队列 {} 的最新数据时间: {}", queueName, now);
        } else {
            log.warn("未找到队列: {}", queueName);
        }
    }

    /**
     * 更新队列状态
     */
    private void updateQueueStatus(QueueInfo queueInfo) {
        LocalDateTime currentTime = LocalDateTime.now();
        LocalDateTime lastDataTime = queueInfo.getLastDataTime();
        
        if (lastDataTime == null) {
            queueInfo.setStatus("NO_DATA");
            queueInfo.setTimeDiffSeconds(null);
        } else {
            long timeDiffSeconds = ChronoUnit.SECONDS.between(lastDataTime, currentTime);
            queueInfo.setTimeDiffSeconds(timeDiffSeconds);
            
            // 判断状态：超过阈值为延迟或无数据
            if (timeDiffSeconds > noDataThresholdSeconds) {
                queueInfo.setStatus("NO_DATA");
            } else if (timeDiffSeconds > delayThresholdSeconds) {
                queueInfo.setStatus("DELAYED");
            } else {
                queueInfo.setStatus("NORMAL");
            }
        }
        
        queueInfo.setUpdateTime(currentTime);
    }
    
    /**
     * 清理过期数据
     */
    public void cleanupExpiredData() {
        LocalDateTime cutoffTime = LocalDateTime.now().minusMinutes(dataRetentionMinutes);
        queueCache.values().forEach(queueInfo -> {
            if (queueInfo.getLastDataTime() != null && 
                queueInfo.getLastDataTime().isBefore(cutoffTime)) {
                // 可以根据需要重置队列状态或保留历史记录
                log.debug("清理队列 {} 的过期数据", queueInfo.getQueueName());
            }
        });
    }
}